<script setup lang="ts">
import {computed, nextTick, onMounted, reactive, ref, useSlots, watch, shallowRef} from "vue";
import store from '@/store';
import Search from './search.vue';
import ColumnRender from "./column-render.vue";
import {RenderScope, TableColumnActions, TableColumnContext, DataTableProps} from './interface'
import {service, replaceClass} from "@/utils";
import {ElButton, ClickOutside as vClickOutside, TableInstance, ElTag} from "element-plus";
import ContextMenu, {ContextmenuProps} from '@/components/right-click-menu/index.vue';
import SvgIcon from "@/components/svg-icon/index.vue";

const {application} = store.globalStore;

const props = withDefaults(defineProps<DataTableProps>(), {
    api: undefined,
    data: undefined,
    height: '100%',
    index: false,
    border: true,
    stripe: false,
    pageSize: 10,
    searchPosition: 'auto',
    lazy: false,
    pagination: true,
    selection: false,
    primaryKey: 'id',
    selectOnRowClick: false,
    beforeOpenContextMenu: () => true
})
const slots = useSlots() as any;

const params = defineModel("params");

const emits = defineEmits(['rowDbclick', 'loading'])

const tableRef = ref<TableInstance>();
const properties = reactive({
    loading: false,
    loadingText: '正在加载...',
    current: undefined,
    selections: [],
    data: {
        rows: [],
        total: 0,
    },
    pagination: {
        enabled: props.pagination, // 是否开启分页
        pageSize: props.pageSize,
        pageNum: 1,
        sort: ''
    },
    handle: {
        loadLocalData: (data: any) => {
            properties.data.rows = data?.rows ?? data;
            properties.data.total = data?.total ?? data.length;
        },
        loadRemoteData: (final?: () => void): void => {
            if (props.api) {
                properties.handle.loading(true, 200);
                tableRef.value?.clearSelection();//加载前固定清空已选数据
                const ps = {...properties.pagination} //基础参数
                params.value && Object.assign(ps, params.value); //合并参数（被动获取参数）
                console.log('发送参数：' + JSON.stringify(ps));
                service.get(props.api, ps).then(({code, data}) => {
                    if (code === 200) {
                        properties.data = data;
                    } else {
                        properties.data = {rows: [], total: 0};
                    }
                    properties.handle.loading(false, code)
                }).catch(() => {
                    properties.data = {rows: [], total: 0};
                    properties.handle.loading(false, 400)
                }).finally(final);
            }
        },
        loading: (status: boolean, code: number) => {
            properties.loading = status;
            emits('loading', status, code);
        },
        sizeChange: (size: number) => {
            properties.pagination.pageSize = size;
            properties.pagination.pageNum = 1;
            properties.handle.loadRemoteData();
        },
        currentPageChange: (num: number) => {
            properties.pagination.pageNum = num;
            properties.handle.loadRemoteData();
        },
        // 复选框-选中行
        selectionChange: (rows: any) => {
            properties.selections = rows || [];
        },
        // 行-单击事件
        rowClick: (row: any, column: any, event: MouseEvent) => {
            event.preventDefault();
            event.stopPropagation();
            onClickRow(event, row);
        },
        rowDblClick: (row: { [key: string]: any }) => {
            emits('rowDbclick', row)
            if (props.selectOnRowClick && props.primaryKey) {
                tableRef.value?.clearSelection();
                tableRef.value?.toggleRowSelection(row, undefined);
            }
        },
        // 排序
        sortChange: (column: any) => {
            if (column.order) {
                properties.pagination.sort = column.prop + ':' + column.order;
            } else {
                properties.pagination.sort = '';
            }
        },
        // 右键菜单
        rowContextMenu: (row: any, column: any, event: MouseEvent) => {
            //右键菜单
            // event.preventDefault();
            // event.stopPropagation();
            // onOpenContextMenu(event, row);
            event.preventDefault();
            event.stopPropagation();
            contextmenu.onOpen(event, row);
        },
        rowClassName(data: { row: never, rowIndex: number }) {
            if (props.selection && properties.selections.includes(data.row)) {
                return 'current-row'
            }
            return ''
        }
    }
})
const tableConfig = reactive({
    index: props.index,
    size: 'default',
    border: props.border,
    stripe: props.stripe,
    buttonStyle: 'round',
    actionColumn: true,
})

const onClickRow = (event: MouseEvent, row?: any) => {
    if (!row) {
        tableRef.value?.setCurrentRow(null);
    }
    // 存在复选框时，点击一行则默认选中当前行
    if (props.selection && props.selectOnRowClick && props.primaryKey) {
        tableRef.value?.clearSelection();
        if (!!row) {
            tableRef.value?.toggleRowSelection(row, undefined);
        }
    }
}

// 刷新数据
const onRefresh = (data?: any) => {
    if (typeof data !== 'undefined') {
        // 该逻辑根据业务需求自定义即可
        if (data.code === 200) {
            // 此处逻辑直接衔接表单关闭之后的操作
            if (typeof data.data === 'string' && data.data === 'cancel') {
                tableRef.value?.clearSelection(); // 取消提交请求
            } else if (data.rows || data instanceof Array) {
                properties.handle.loadLocalData(data);
            } else {
                properties.handle.loadRemoteData(); // 提交请求并返回成功
            }
        } else if (data.rows || data instanceof Array) {
            properties.handle.loadLocalData(data);
        }
    } else {
        properties.handle.loadRemoteData();
    }
}

//刷新后定位
const onRefreshAndLocate = (target: any) => {
    if (props.primaryKey && target) {
        properties.handle.loadRemoteData(() => {
            let item = properties.data.rows.find(o => o[props.primaryKey] === target);
            if (item) {
                tableRef.value?.setCurrentRow(item);
                tableRef.value?.toggleRowSelection(item, undefined);
            }
        });
    }
}

/************************** 操作按钮 ********************************/
let btnElement:any;
const vTooltipButton = {
    created:(el: any) => {
        btnElement = el;
    },
    mounted: (el: any) => {
        nextTick(() => {
            for (const item of btnElement.children) {
                // const list = item.classList as DOMTokenList;
                // const ts = ['plain', 'round', 'circle'];
                // for (let type of ts) {
                //     if (list.contains(`is-${type}`)) {
                //         replaceClass(item, `is-${type}`, '');
                //     }
                // }
                replaceClass(item, '', `is-${tableConfig.buttonStyle}`);
                changeButtonStyle(tableConfig.buttonStyle, item);
            }
        })
    },
    updated: () => {
        // 如果按钮‘disabled’是动态的话，按钮在切换状态时会变成默认按钮
        for (const item of btnElement.children) {
            replaceClass(item, '', `is-${tableConfig.buttonStyle}`);
        }
    }
}
watch(() => tableConfig.buttonStyle, (type1, type2) => {
    for (const item of btnElement.children) {
        if (item.localName === 'button') {
            changeButtonStyle(type1, item);
            replaceClass(item, `is-${type2}`, `is-${type1}`);
        }
    }
})

function changeButtonStyle(type: string, item: any) {
    if (item.localName === 'button') {
        if (type === 'circle') {
            if (!item.title) {
                item.title = item.innerText;
            }
            item.lastChild.localName === 'span' && item.removeChild(item.lastChild)
        } else {
            if (item.lastChild.localName !== 'span') {
                const span = document.createElement('span');
                span.innerText = item.title;
                item.appendChild(span);
            }
            item.removeAttribute('title');
        }
    }
}


/************************ 自定义列隐藏/显示以及操作列定义 ************************/
const allColumns = props.columns?.filter(o => !!o.prop)?.map((o, index) => {
    if(!o.hasOwnProperty('visible')) {
        o.visible = true;
    }
    o.no = index;
    return o;
}) ?? [];
const dynamicsColumn = reactive({
    visible: false,
    columns: allColumns,
    checkAll: allColumns.every(o => o.visible === true),
    isIndeterminate: allColumns.some(o => o.visible === true) && allColumns.some(o => o.visible === false),
    handle: {
        checkAllChange: (value: any) => {
            dynamicsColumn.columns.filter(o => !o.fixed).forEach(o => o.visible = value);
            dynamicsColumn.handle.checkedChange();
        },
        checkedChange: () => {
            dynamicsColumn.checkAll = dynamicsColumn.columns.every(o => o.visible === true);
            dynamicsColumn.isIndeterminate = dynamicsColumn.columns.some(o => o.visible === true) && dynamicsColumn.columns.some(o => o.visible === false);
        },
        sortable: (item: any, sort: string, index: number) => {
            if (dynamicsColumn.columns) {
                let number;
                if (sort === 'up' && index > 0) {
                    number = dynamicsColumn.columns[index].no as number;
                    dynamicsColumn.columns[index].no = number - 1;

                    number = dynamicsColumn.columns[index - 1].no as number;
                    dynamicsColumn.columns[index - 1].no = number + 1;
                } else if (sort === 'down' && index < dynamicsColumn.columns.length - 1) {
                    number = dynamicsColumn.columns[index].no as number
                    dynamicsColumn.columns[index].no = number + 1;

                    number = dynamicsColumn.columns[index + 1].no as number;
                    dynamicsColumn.columns[index + 1].no = number - 1;
                }
                dynamicsColumn.columns.sort((o1, o2) => (o1.no ?? 0) - (o2.no ?? 0));
            }
        }
    }
})
// 操作列
const actionColumn = ref<TableColumnContext|undefined>(props.columns?.find(o => o.type === 'action'));
const showActions = ref<TableColumnActions[]>([]);
const moreActions = ref<TableColumnActions[]>([]);
const moreAuths = ref<string[]>([]);
const moreActionRf = ref();
const moreActionVisible = ref(false);
const actionColumnScope = ref();
if (actionColumn.value && typeof actionColumn.value.render === 'object') {
    const list = actionColumn.value.render as TableColumnActions[];
    const max = ((actionColumn.value.maxCollapseButtons ?? 0) > 0? actionColumn.value.maxCollapseButtons:list.length) as number;
    showActions.value = list.filter((o, j) => j < max);
    moreActions.value = list.filter((o, j) => j >= max);
    moreAuths.value = moreActions.value.map(o => o.auth? o.auth:'');
}
const onMoreAction = (event: PointerEvent, scope: RenderScope) => {
    actionColumnScope.value = scope;
    moreActionRf.value = event.target
    nextTick(() => moreActionVisible.value = true);
}
const onMoreActionClickOutside = () => {
    // 有多少行数据，该函数就会执行多少次
    if (moreActionVisible.value) {
        moreActionVisible.value = false;
    }
}
// Popover隐藏动画播放完毕后触发，利用动画播放时间差清空选中对象操作。如果onMoreActionClickOutside函数做清空操作会导致执行事件时取不到数据
const onMoreActionPopoverLeave = () => {
    actionColumnScope.value = undefined;
    moreActionRf.value = undefined;
}

/*************************** 查询框 ********************************/
const searchFormRef = ref();
const hasSearchSlot = ref(slots.hasOwnProperty('search')); // 是否存在查询框
const collapsed = ref<boolean|undefined>(undefined); // 查询框是否折叠
const _searchPosition = computed(() => {
    // 计算查询框的位置（顶部/左侧）
    let position = undefined;
    if (props.searchPosition === 'auto') {
        const count = Object.keys(params.value || {}).length;
        if (count >= 5) {
            position = 'top';
        } else if (count > 0 && count < 5){
            position = 'left';
        }
    } else {
        position = props.searchPosition;
    }
    return position;
});
const onReset = () => {
    searchFormRef.value.resetFields();
    nextTick(() => onRefresh());
}
const onCollapsed = () => {
    collapsed.value = !collapsed.value;
}
const onChangeCollapsed = (el: HTMLElement, value: boolean|undefined) => {
    if (_searchPosition.value === 'left') {
        topSearchHeight.value = '0px';
    } else {
        topSearchHeight.value = (value === false? el.clientHeight:el.children[0].clientHeight) + 10 + 'px';
    }
}

/************************** 右键菜单 ********************************/
const contextmenu = reactive<ContextmenuProps>({
    data: {
        position: [0, 0],
        parameter: []
    },
    menus: [
        {
            id: 'refresh',
            label: '刷新',
            icon: 'icon-refresh',
            hidden: !props.api,
            onClick: () => {
                onRefresh();
            }
        },
        {
            id: 'custom_column',
            label: "自定义列",
            icon: 'icon-filter',
            hidden: !props.columns,
            onClick: () =>  {
                dynamicsColumn.visible = true;
            }
        },
        {separator: true},
        {
            label: "设置",
            icon: 'icon-setting',
            children: [
                {
                    id: 'index',
                    label: '显示序号',
                    onClick: (data: any, menu: any) =>  {
                        menu.icon = (tableConfig.index = !tableConfig.index)? 'icon-check':'';
                    }
                },
                {
                    id: 'border',
                    label: '显示边框',
                    onClick: (data: any, menu: any) =>  {
                        menu.icon = (tableConfig.border = !tableConfig.border)? 'icon-check':'';
                    }
                },
                {
                    id: 'stripe',
                    label: '显示条纹',
                    onClick: (data: any, menu: any) =>  {
                        menu.icon = (tableConfig.stripe = !tableConfig.stripe)? 'icon-check':'';
                    }
                },
                {
                    id: 'actionColumn',
                    label: '显示操作列',
                    onClick: (data: any, menu: any) =>  {
                        menu.icon = (tableConfig.actionColumn = !tableConfig.actionColumn)? 'icon-check':'';
                    }
                },
                {separator: true},
                {
                    label: '表格尺寸',
                    children: [
                        {
                            id: 'table_size_large',
                            label: '偏大',
                            onClick: () =>  {
                                tableConfig.size = 'large';
                            }
                        },
                        {
                            id: 'table_size_default',
                            label: '常规',
                            onClick: () =>  {
                                tableConfig.size = 'default';
                            }
                        },
                        {
                            id: 'table_size_small',
                            label: '偏小',
                            onClick: () =>  {
                                tableConfig.size = 'small';
                            }
                        },
                    ]
                },
                {
                    label: '按钮样式',
                    children: [
                        {
                            id: 'table_button_plain',
                            label: '朴素按钮',
                            onClick: () => {
                                tableConfig.buttonStyle = 'plain';
                            }
                        },
                        {
                            id: 'table_button_circle',
                            label: '圆形按钮',
                            click: () => {
                                tableConfig.buttonStyle = 'circle';
                            }
                        },
                        {
                            id: 'table_button_round',
                            label: '圆角按钮',
                            click: () => {
                                tableConfig.buttonStyle = 'round';
                            }
                        }
                    ]
                },
            ]
        },
    ],
    // 打开菜单前触发事件
    onBeforeOpen: (parameter: any, menus: Array<any>) => {
        menus.forEach((item: any) => {
            switch (item.id) {
                case 'index':
                    item.icon = tableConfig.index? 'icon-check':''
                    break;
                case 'border':
                    item.icon = tableConfig.border? 'icon-check':''
                    break;
                case 'stripe':
                    item.icon = tableConfig.stripe? 'icon-check':''
                    break;
                case 'actionColumn':
                    item.icon = tableConfig.actionColumn? 'icon-check':''
                    break;
                case 'table_size_large':
                    item.icon = tableConfig.size === 'large'? 'icon-check':''
                    break;
                case 'table_size_default':
                    item.icon = tableConfig.size === 'default'? 'icon-check':''
                    break;
                case 'table_size_small':
                    item.icon = tableConfig.size === 'small'? 'icon-check':''
                    break;
                case 'table_button_plain':
                    item.icon = tableConfig.buttonStyle === 'plain'? 'icon-check':''
                    break;
                case 'table_button_circle':
                    item.icon = tableConfig.buttonStyle === 'circle'? 'icon-check':''
                    break;
                case 'table_button_round':
                    item.icon = tableConfig.buttonStyle === 'round'? 'icon-check':''
                    break;
            }
        })
        return props.beforeOpenContextMenu(parameter, menus) || true;
    },
    // 打开菜单,使用地方：hadoop
    onOpen: (event: MouseEvent, row?: any) => {
        tableRef.value?.setCurrentRow(row);
        if (!!row) {
            // 文件资源-右键在非选中行上点击则取消已选中的所有行，同时选中当前行
            let rs = properties.selections?.filter((o: any) => o[props.primaryKey] === row[props.primaryKey]);
            if (rs.length === 0) {
                tableRef.value?.clearSelection();
                tableRef.value?.toggleRowSelection(row, true, false);
                contextmenu.data.parameter = {current: row, selections: [row]}
            } else {
                contextmenu.data.parameter = {current: row, selections: properties.selections}
            }
        } else {
            tableRef.value?.clearSelection();
            contextmenu.data.parameter = {current: undefined, selections: []}
        }
        nextTick(() => contextmenu.data.position = [event.clientX, event.clientY])
    },
})

if (props.contextMenuExtra) {
    if (Array.isArray(props.contextMenuExtra)) {
        contextmenu.menus.splice(1, 0, ...props.contextMenuExtra);
    }
}


/************************** 表格高度 ********************************/
const _height = computed(() => Number(props.height) ? Number(props.height) + 'px' : props.height);
const zoneHeight = computed(() => application.size === 'large'? '50px':application.size === 'small'? '34px':'42px');
const topSearchHeight = ref("0px");
const tableHeight = computed(() => "calc(100% - " + zoneHeight.value + " * " + (props.pagination? 2:1) + " - " + topSearchHeight.value +  ")")


// 自动加载表数据
onMounted(() => {
    nextTick(() => !props.lazy && !!props.api && onRefresh())
})

// 暴露给父组件的参数和方法 (外部需要什么，都可以从这里暴露出去)
defineExpose({
    refresh: onRefresh,
    refreshAndLocate: onRefreshAndLocate,
})

</script>

<template>
    <div v-loading="properties.loading" :style="{ 'height': _height }" class="kt-table" style="overflow: hidden" @contextmenu.prevent.stop  @click.prevent.stop>
        <div v-if="_searchPosition === 'top'" class="kt-table-search" :style="{'height': topSearchHeight}">
            <search v-model="params" v-model:collapse="collapsed" v-model:form-ref="searchFormRef" :abreast="false" :size="application.size"
                    @change-collapse="onChangeCollapsed">
                <slot name="search"/>
            </search>
        </div>
        <div class="kt-table-header" :style="{'height': zoneHeight}">
            <div class="kt-table-header__left" v-if="_searchPosition === 'left'" >
                <search v-model="params" v-model:form-ref="searchFormRef" :abreast="true" :size="application.size"
                        @change-collapse="onChangeCollapsed">
                    <slot name="search"/>
                </search>
            </div>
            <div class="kt-table-header__left" v-else v-tooltip-button>
                <slot :selections="properties.selections" name="extra"/>
            </div>
            <div class="kt-table-header__right" v-tooltip-button>
                <el-button v-if="!!api" :icon="hasSearchSlot? 'el-icon-search':'el-icon-refresh'" :title="hasSearchSlot? '查询':'刷新'" @click="onRefresh()"/>
                <el-button v-if="!!api && hasSearchSlot" :icon="'el-icon-refresh-left'" :title="'重置'" @click="onReset()"/>
                <slot :selections="properties.selections" name="button"/>
                <el-button v-if="collapsed !== undefined" :icon="collapsed? 'el-icon-arrow-down':'el-icon-arrow-up'" :title="'展开/折叠查询'" @click="onCollapsed()"/>
            </div>
        </div>
        <div :style="{'height': tableHeight}" @contextmenu.prevent.stop="contextmenu.onOpen" @click.prevent.stop="onClickRow">
            <el-table ref="tableRef"
                      :border="tableConfig.border"
                      :data="data || properties.data.rows"
                      :height="height == 'auto' ? null : '100%'"
                      :tooltip-options="{'popper-class': 'kt-table-tooltip'}"
                      :row-key="primaryKey"
                      :size="tableConfig.size"
                      :stripe="tableConfig.stripe"
                      :highlight-current-row="true"
                      @row-contextmenu="properties.handle.rowContextMenu"
                      @row-click="properties.handle.rowClick"
                      @row-dblclick="properties.handle.rowDblClick"
                      @selection-change="properties.handle.selectionChange"
                      @sort-change="properties.handle.sortChange"
                      :row-class-name="properties.handle.rowClassName"
                      v-bind="$attrs">
                <el-table-column v-if="selection" align="center" fixed="left" header-align="center" type="selection" width="55"/>
                <el-table-column v-if="tableConfig.index" align="left" fixed="left" header-align="center" label="序 号" type="index" width="70">
                    <template #default="{ $index }">
                        {{ $index + 1 }}
                    </template>
                </el-table-column>
                <slot></slot>
                <template v-for="(column, index) in dynamicsColumn.columns" :key="`column_${index}`">
                    <el-table-column v-if="column.visible !== false && column.type !== 'action'"
                                     :column-key="column.prop"
                                     :align="column.align? column.align:column.tag? 'center':'left'"
                                     :fixed="column.fixed"
                                     :label="column.label"
                                     :prop="column.prop"
                                     :resizable="column.resizable"
                                     :header-align="'center'"
                                     :show-overflow-tooltip="column.tooltip"
                                     :sortable="column.sortable"
                                     :width="column.width">
                        <template v-if="column.render && typeof column.render === 'function'" #default="scope">
                            <column-render :scope="scope" :render="column.render"/>
                        </template>
                        <template v-if="column.tag && column.prop" #default="scope">
                            <div v-for="(option, ti) in (column.options || enums[column.prop])" :key="ti">
                                <transition mode="out-in">
                                    <component v-if="scope.row[column.prop] === option.value" :is="ElTag" v-bind="option">{{ option['label'] }}</component>
                                </transition>
                            </div>
                        </template>
                    </el-table-column>
                </template>
                <el-table-column v-if="actionColumn && tableConfig.actionColumn"
                                 :align="actionColumn.align? actionColumn.align:'center'"
                                 :fixed="actionColumn.fixed? actionColumn.fixed:'right'"
                                 :label="actionColumn.label? actionColumn.label:'操作'"
                                 :width="actionColumn.width">
                    <template v-if="showActions.length > 0" #default="scope">
                        <el-button v-for="item in showActions" v-auth="item.auth" :type="item.type || 'primary'" @click="item.onClick(scope)" link>
                            <template v-if="item.icon" #icon>
                                <svg-icon :icon="item.icon"/>
                            </template>
                            {{item.label}}
                        </el-button>
                        <el-button v-if="moreActions.length > 0" v-auth:or="moreAuths" v-click-outside="onMoreActionClickOutside" link @click="onMoreAction($event, scope)">
                            <template #icon>
                                <svg-icon icon="icon-more" style="transform: rotate(90deg);"/>
                            </template>
                            更多
                        </el-button>
                    </template>
                    <template v-else #default="scope">
                        <column-render :scope="scope" :render="actionColumn.render"/>
                    </template>
                </el-table-column>
                <template #empty>
                    <el-empty :description="'暂无数据'" :image-size="100"/>
                </template>
            </el-table>
        </div>
        <div v-if="properties.pagination.enabled" class="kt-table-footer" :style="{'height': zoneHeight}">
            <div class="kt-table-footer__right">
                <el-pagination v-if="properties.pagination.enabled"
                               :background="true"
                               :current-page="properties.pagination.pageNum"
                               :disabled="properties.loading"
                               :page-size="properties.pagination.pageSize"
                               :page-sizes="[10, 20, 50, 100, 200, 500]"
                               :pager-count="9"
                               :total="properties.data?.total || 0"
                               layout="total, sizes, prev, pager, next, jumper"
                               @size-change="properties.handle.sizeChange"
                               @current-change="properties.handle.currentPageChange"/>
            </div>
        </div>
        <context-menu v-model="contextmenu.menus" :before-open="contextmenu.onBeforeOpen" :data="contextmenu.data"/>

        <el-popover v-if="showActions.length > 0" :placement="'bottom-end'" :trigger="'click'" :virtual-ref="moreActionRf" :virtual-triggering="true" :visible="moreActionVisible"
                    popper-style="padding: 2px 0"
                    @after-leave="onMoreActionPopoverLeave">
            <div class="kt-more-button">
                <el-button v-for="(action, index) in moreActions" v-auth="action.auth" :key="index" text @click="action.onClick(actionColumnScope)">
                    <template v-if="action.icon" #icon>
                        <svg-icon :icon="action.icon"/>
                    </template>
                    {{ action.label }}
                </el-button>
            </div>
        </el-popover>

        <el-drawer v-model="dynamicsColumn.visible" title="自定义列" direction="rtl" size="20%">
            <div class="kt-full" style="padding: 0 10px">
                <el-checkbox v-model="dynamicsColumn.checkAll" :label="'全部'" :indeterminate="dynamicsColumn.isIndeterminate" @change="dynamicsColumn.handle.checkAllChange"/>
                <ul class="kt-dynamics-column">
                    <li v-for="(box, bid) in dynamicsColumn.columns" :key="bid" >
                        <div style="display: flex;">
                            <el-checkbox v-model="box.visible" :label="box.label" :disabled="!!box?.fixed" @change="dynamicsColumn.handle.checkedChange"/>
                        </div>
                        <div style="display: flex">
                            <el-button icon="el-icon-sort-down" :plain="true" :disabled="!!box?.fixed" @click="dynamicsColumn.handle.sortable(box, 'down', bid)"></el-button>
                            <el-button icon="el-icon-sort-up" :plain="true" :disabled="!!box?.fixed" @click="dynamicsColumn.handle.sortable(box, 'up', bid)"></el-button>
                        </div>
                    </li>
                </ul>
            </div>
        </el-drawer>
    </div>
</template>
<style>
div:has(> .el-overlay-dialog .el-dialog.search-panel) {
    height: 0;
}
.el-overlay-dialog:has(> .el-dialog.search-panel) {
    overflow: unset;
    height: 0;
}

.kt-table-header__left .el-form--inline .el-form-item {
    margin-bottom: 0;
    margin-right: 0
}
</style>
<style lang="scss" scoped>
.kt-table {
    --el-fill-color-lighter: var(--el-color-primary-light-9);
}

.kt-table-search {
    width: 100%;
    transition: height 0.2s ease-out;
    overflow: hidden;
}

.kt-table-header {
    display: flex;
    align-items: center;

    &__left {
        flex: 1;
    }

    &__right {
        display: flex;
        justify-content: right;
        align-items: center;

        :deep(.el-button + .el-button) {
            margin-left: 5px;
        }
    }
}

.kt-table-footer {
    display: flex;
    align-items: center;
    position: relative;

    &__right {
        margin: 0 5px;
        position: absolute;
        right: 0;
    }
}

.kt-more-button {
    width: 100%;

    .el-button + .el-button{
        margin: 5px 0;
    }

    .el-button {
        width: 100%;
        justify-content: flex-start;
    }
}

.kt-dynamics-column {
    li {
        display: inline-flex;
        align-items: center;
        line-height: 50px;
        width: 100%;
        justify-content: space-between;
        /*box-shadow: 0 0 0 1px var(--el-input-border-color, var(--el-border-color)) inset;*/
    }

    li + li {
        margin-top: 5px;
    }
}
</style>
